//
//  NSString+MSString.m
//  Minweixian
//
//  Created by iOS on 2017/5/9.
//  Copyright © 2017年 GSKJ. All rights reserved.
//

#import "NSString+MSString.h"
#import <CommonCrypto/CommonDigest.h>

@implementation NSString (MSString)

/** 去除所有空格 */
- (NSString *)ms_removeAllSpaces
{
    return [[self componentsSeparatedByCharactersInSet:[NSCharacterSet whitespaceCharacterSet]] componentsJoinedByString:@""];
}

/** 去除首尾空格和换行 */
-(NSString *)ms_removeleadingAndTrailingSpaces
{
    return [self stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
}
/** 去除html标签 */
- (NSString *)removeHTMLTags
{
    NSString *htmlString = [self mutableCopy];
    NSRegularExpression *regularExpretion = [NSRegularExpression regularExpressionWithPattern:@"<[^>]*>|\n"
                                                                                      options:0
                                                                                        error:nil];
    htmlString = [regularExpretion stringByReplacingMatchesInString:htmlString
                                                            options:NSMatchingReportProgress
                                                              range:NSMakeRange(0, htmlString.length)
                                                       withTemplate:@""];
    return htmlString;
}
/** 根据html获取html标签文本（异步） */
- (void)ms_HTMLTagsStringWithUrl:(NSString *)urlString
               completionHandler:(NSString *(^)(NSString *htmlString))completionHandler
{
    // 创建URL对象
    NSURL *URL = [NSURL URLWithString:urlString];
    // 创建请求对象
    NSURLRequest *request = [NSURLRequest requestWithURL:URL];
    // 默认的URLSession
    NSURLSession *session = [NSURLSession sharedSession];
    // 创建任务来执行请求
    NSURLSessionDataTask *task = [session dataTaskWithRequest:request completionHandler:
        ^(NSData *_Nullable data, NSURLResponse *_Nullable response, NSError *_Nullable error) {
            // 确保没有错误发生，并且得到了数据
            if (!error && data) {
                // 将数据转换为字符串
                NSString *htmlString = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
                // 输出HTML内容
                MSLog(@"%@", htmlString);
                completionHandler(htmlString);
            } else {
                MSLog(@"Error: %@", error.localizedDescription);
            }
        }];
    // 启动任务
    [task resume];
}
/** HTML适配图片文字 */
- (NSString *)adaptWebViewForHtml
{
    NSString *htmlStr = [self mutableCopy];
    NSMutableString *headHtml = [[NSMutableString alloc] initWithCapacity:0];
    [headHtml appendString : @"<html>" ];
    [headHtml appendString : @"<head>" ];
    [headHtml appendString : @"<meta charset=\"utf-8\">" ];
    [headHtml appendString : @"<meta id=\"viewport\" name=\"viewport\" content=\"width=device-width,initial-scale=1.0,maximum-scale=1.0,user-scalable=false\" />" ];
    [headHtml appendString : @"<meta name=\"apple-mobile-web-app-capable\" content=\"yes\" />" ];
    [headHtml appendString : @"<meta name=\"apple-mobile-web-app-status-bar-style\" content=\"black\" />" ];
    [headHtml appendString : @"<meta name=\"black\" name=\"apple-mobile-web-app-status-bar-style\" />" ];
 
    //适配图片宽度，让图片宽度等于屏幕宽度
    //[headHtml appendString : @"<style>img{width:100%;}</style>" ];
    //[headHtml appendString : @"<style>img{height:auto;}</style>" ];
    
     //适配图片宽度，让图片宽度最大等于屏幕宽度
//    [headHtml appendString : @"<style>img{max-width:100%;width:auto;height:auto;}</style>"];
 
   //适配图片宽度，如果图片宽度超过手机屏幕宽度，就让图片宽度等于手机屏幕宽度，高度自适应，如果图片宽度小于屏幕宽度，就显示图片大小
    [headHtml appendString : @"<script type='text/javascript'>"
     "window.onload = function(){\n"
     "var maxwidth=document.body.clientWidth;\n" //屏幕宽度
     "for(i=0;i <document.images.length;i++){\n"
     "var myimg = document.images[i];\n"
     "if(myimg.width > maxwidth){\n"
     "myimg.style.width = '100%';\n"
     "myimg.style.height = 'auto'\n;"
     "}\n"
     "}\n"
     "}\n"
     "</script>\n"];
    
    [headHtml appendString : @"<style>table{width:100%;}</style>" ];
    [headHtml appendString : @"<title>webview</title>" ];
    NSString *bodyHtml;
    bodyHtml = [NSString stringWithString:headHtml];
    bodyHtml = [bodyHtml stringByAppendingString:htmlStr];
    return bodyHtml;
    
}
/** 获取网站参数 */
- (NSMutableDictionary *)ms_getURLParameters
{
    if ([self containsString:@"?"])
    {
        NSMutableDictionary *parametersDic = [NSMutableDictionary dictionary];
        NSRange range = [self rangeOfString:@"?"];
        /// 取出？后面的参数字符串
        NSString *parametersString = [self substringFromIndex:range.location + 1];
        
        if ([parametersString containsString:@"&"])
        {
            /// 多参
            NSArray<NSString *> *parametersArr = [parametersString componentsSeparatedByString:@"&"];
            
            [parametersArr enumerateObjectsUsingBlock:^(NSString * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
                NSArray *pairComponents = [obj componentsSeparatedByString:@"="];
                NSString *key = [[pairComponents firstObject] stringByRemovingPercentEncoding];
                NSString *value = [[pairComponents lastObject] stringByRemovingPercentEncoding];
                
                if (key && value)
                {
                    [parametersDic setObject:value forKey:key];
                }
            }];
        }
        else
        {
            /// 单参
            NSArray *pairComponent = [parametersString componentsSeparatedByString:@"="];
            NSString *key = [[pairComponent firstObject] stringByRemovingPercentEncoding];
            NSString *value = [[pairComponent lastObject] stringByRemovingPercentEncoding];
            if (key && value)
            {
                [parametersDic setObject:value forKey:key];
            }
            else
            {
                return nil;
            }
        }
        
        return parametersDic;
    }
    else
    {
        return nil;
    }
}

- (NSString *)ms_formatOneDecimal
{
    NSDecimalNumber *number = [NSDecimalNumber decimalNumberWithString:ms_stringIsEmpty(self) ? @"0" : self];
    NSNumberFormatter *formatter = [[NSNumberFormatter alloc] init];
    formatter.positiveFormat = @"0.0";
    return [formatter stringFromNumber:number];
}

- (NSString *)ms_formatTwoDecimal
{
    NSDecimalNumber *number = [NSDecimalNumber decimalNumberWithString:ms_stringIsEmpty(self) ? @"0" : self];
    NSNumberFormatter *formatter = [[NSNumberFormatter alloc] init];
    formatter.positiveFormat = @"0.00";
    return [formatter stringFromNumber:number];
}

- (BOOL)ms_isHasChinese
{
    for (int i = 0; i < self.length; i++)
    {
        if ((int)[self characterAtIndex:i] > 127)
        {
            return YES;
        }
    }
    
    return NO;
}

- (NSString *)ms_stringDisposeRemoveFloatAllZero
{
    return [NSString stringWithFormat:@"%@", @(self.floatValue)];
}


#pragma mark - 复制到粘贴板
/** 复制到粘贴板 */
- (void)ms_copyToPasteboard
{
    UIPasteboard *pasteBoard = [UIPasteboard generalPasteboard];
    pasteBoard.string = self;
}


#pragma mark - 字符转换
-(NSString *)ms_toLower
{
    NSString *str = [NSString stringWithString:self];
    
    for (NSInteger i = 0; i < str.length; i++)
    {
        if ([str characterAtIndex:i] >= 'A' && [str characterAtIndex:i]<='Z')
        {
            //A  65  a  97
            char  temp = [str characterAtIndex:i] + 32;
            NSRange range = NSMakeRange(i, 1);
            str = [str stringByReplacingCharactersInRange:range
                                               withString:[NSString stringWithFormat:@"%c",temp]];
        }
    }
    return str;
}

-(NSString *)ms_toUpper
{
    NSString *str = [NSString stringWithString:self];
    
    for (NSInteger i = 0; i < str.length; i++)
    {
        if ([str characterAtIndex:i] >= 'a' && [str characterAtIndex:i] <= 'z')
        {
            //A  65  a  97
            char  temp = [str characterAtIndex:i] - 32;
            NSRange range = NSMakeRange(i, 1);
            str = [str stringByReplacingCharactersInRange:range
                                               withString:[NSString stringWithFormat:@"%c", temp]];
        }
    }
    
    return str;
}

- (NSString *)ms_transformPinYin
{
    NSString *pinYinStr = [NSString string];
    
    if (self.length)
    {
        NSMutableString *pinYin = [NSMutableString stringWithString:self];
        
        // 1、先转换为带声调的拼音
        if (CFStringTransform((__bridge CFMutableStringRef)pinYin, NULL, kCFStringTransformMandarinLatin, NO)) {
            MSLog(@"带声调的拼音：%@", pinYin);
        }
        
        // 2、在转换为不带声调的拼音
        if (CFStringTransform((__bridge CFMutableStringRef)pinYin, NULL, kCFStringTransformStripDiacritics, NO)) {
            MSLog(@"不带声调的拼音：%@", pinYin);
        }
        
        // 3.去除掉首尾的空白字符和换行字符
        pinYinStr = [pinYin stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
    }
    
    return pinYinStr;
}


#pragma mark - 版本号比较
/// 版本号比较,返回较大的版本号信息
/// @param version2 版本号信息2
- (NSString *)ms_compareVersionWithVersion2:(NSString *)version2
{
    // 获取各个版本号对应版本信息
    NSMutableArray *versionStep1 = [NSMutableArray arrayWithArray:[self componentsSeparatedByString:@"."]];
    NSMutableArray *versionStep2 = [NSMutableArray arrayWithArray:[version2 componentsSeparatedByString:@"."]];
    
    // 补全版本信息为相同位数
    while (versionStep1.count < versionStep2.count)
    {
        [versionStep1 addObject:@"0"];
    }
    
    while (versionStep2.count < versionStep1.count)
    {
        [versionStep2 addObject:@"0"];
    }
    
    // 遍历每一个版本信息中的位数
    // 记录比较结果值
    BOOL compareResutl = NO;
    for(NSUInteger i = 0; i < versionStep1.count; i++)
    {
        NSInteger versionNumber1 = [versionStep1[i] integerValue];
        NSInteger versionNumber2 = [versionStep2[i] integerValue];
        if (versionNumber1 < versionNumber2)
        {
            compareResutl = YES;
            break;
        }
        else if (versionNumber2 < versionNumber1)
        {
            compareResutl = NO;
            break;
        }
        else
        {
            compareResutl = NO;
        }
    }
    
    return compareResutl ? version2 : self;
}

- (NSComparisonResult)ms_compareVersion:(NSString *)version
{
    // 获取各个版本号对应版本信息
    NSMutableArray *versionStep1 = [NSMutableArray arrayWithArray:[self componentsSeparatedByString:@"."]];
    NSMutableArray *versionStep2 = [NSMutableArray arrayWithArray:[version componentsSeparatedByString:@"."]];
    
    // 补全版本信息为相同位数
    while (versionStep1.count < versionStep2.count)
    {
        [versionStep1 addObject:@"0"];
    }
    
    while (versionStep2.count < versionStep1.count)
    {
        [versionStep2 addObject:@"0"];
    }
    
    // 遍历每一个版本信息中的位数
    // 记录比较结果值
    NSComparisonResult result = NSOrderedSame;
    for(NSUInteger i = 0; i < versionStep1.count; i++)
    {
        NSInteger versionNumber1 = [versionStep1[i] integerValue];
        NSInteger versionNumber2 = [versionStep2[i] integerValue];
        if (versionNumber1 < versionNumber2)
        {
            result = NSOrderedAscending;
            break;
        }
        else if (versionNumber2 < versionNumber1)
        {
            result = NSOrderedDescending;
            break;
        }
        else
        {
            result = NSOrderedSame;
        }
    }
    
    return result;
}


#pragma mark - 常用正则
/** 验证手机号 */
- (BOOL)ms_isValidMobilePhoneNumber
{
    /**
     * 手机号码
     * 移动：134[0-8],135,136,137,138,139,150,151,157,158,159,182,187,188
     * 147，152，183，184
     * 联通：130,131,132,152,155,156,185,186
     * 166，175，176，145
     * 电信：133,1349,153,180,189
     */
    NSString * MOBILE = @"^1(3[0-9]|5[0-35-9]|8[025-9])\\d{8}$";
    
    /**
     * 中国移动：China Mobile
     * 134[0-8],135,136,137,138,139,150,151,157,158,159,182,187,188
     */
    NSString * CM = @"^1(34[0-8]|(3[5-9]|5[0127-9]|8[23478]|4[7])\\d)\\d{7}$";
    
    /**
     * 中国联通：China Unicom
     * 130,131,132,152,155,156,175,176,185,186
     */
    NSString * CU = @"^1(3[0-2]|5[256]|7[56]|8[56]|6[6]|4[5])\\d{8}$";
    
    /**
     * 中国电信：China Telecom
     * 133,1349,153,177,180,189
     */
    NSString * CT = @"^1((33|53|77|8[09]|34)[0-9]|349)\\d{7}$";
    
    /**
     * 大陆地区固话及小灵通
     * 区号：010,020,021,022,023,024,025,027,028,029
     * 号码：七位或八位
     */
    NSString * PHS = @"^0(10|2[0-5789]|\\d{3})\\d{7,8}$";
    
    NSPredicate *regextestmobile = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", MOBILE];
    NSPredicate *regextestcm = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", CM];
    NSPredicate *regextestcu = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", CU];
    NSPredicate *regextestct = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", CT];
    NSPredicate *regextestPHS = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", PHS];
    
    if (([regextestmobile evaluateWithObject:self] == YES)
       || ([regextestcm evaluateWithObject:self] == YES)
       || ([regextestct evaluateWithObject:self] == YES)
       || ([regextestcu evaluateWithObject:self] == YES)
       || ([regextestPHS evaluateWithObject:self] == YES))
    {
        return YES;
    }
    else
    {
        return NO;
    }
}
/** 验证邮箱*/
- (BOOL)ms_isValidEmail
{
    //^(\\w)+(\\.\\w+)*@(\\w)+((\\.\\w{2,3}){1,3})$
    //[A-Z0-9a-z._%+-]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,4} //2020.1.10更换
    //^[a-zA-Z0-9_-]+@[a-zA-Z0-9_-]+(\\.[a-zA-Z0-9_-]+)+$
    NSString *regex = @"[A-Z0-9a-z._%+-]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,4}";
    NSPredicate *emailTest = [NSPredicate predicateWithFormat:@"SELF MATCHES %@", regex];
    
    return [emailTest evaluateWithObject:self];
}
/** 验证身份证号 */
- (BOOL)ms_validIDCardNumber
{
    NSString *value = [self stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
    NSInteger length = 0;
    if (!value)
    {
        return NO;
    }
    else
    {
        length = value.length;
        //不满足15位和18位，即身份证错误
        if (length !=15 && length !=18)
        {
            return NO;
        }
    }
    // 省份代码
    NSArray *areasArray = @[@"11",@"12", @"13",@"14", @"15",@"21", @"22",@"23", @"31",@"32", @"33",@"34", @"35",@"36", @"37",@"41", @"42",@"43", @"44",@"45", @"46",@"50", @"51",@"52", @"53",@"54", @"61",@"62", @"63",@"64", @"65",@"71", @"81",@"82", @"91"];
    
    // 检测省份身份行政区代码
    NSString *valueStart2 = [value substringToIndex:2];
    BOOL areaFlag =NO; //标识省份代码是否正确
    for (NSString *areaCode in areasArray)
    {
        if ([areaCode isEqualToString:valueStart2])
        {
            areaFlag =YES;
            break;
        }
    }
    
    if (!areaFlag)
    {
        return NO;
    }
    
    NSRegularExpression *regularExpression;
    NSUInteger numberofMatch;
    
    int year =0;
    //分为15位、18位身份证进行校验
    switch (length)
    {
        case 15:
            //获取年份对应的数字
            year = [value substringWithRange:NSMakeRange(6,2)].intValue +1900;
            
            if (year %4 ==0 || (year %100 ==0 && year %4 ==0))
            {
                //创建正则表达式 NSRegularExpressionCaseInsensitive：不区分字母大小写的模式
                regularExpression = [[NSRegularExpression alloc]initWithPattern:@"^[1-9][0-9]{5}[0-9]{2}((01|03|05|07|08|10|12)(0[1-9]|[1-2][0-9]|3[0-1])|(04|06|09|11)(0[1-9]|[1-2][0-9]|30)|02(0[1-9]|[1-2][0-9]))[0-9]{3}$"
                                                                        options:NSRegularExpressionCaseInsensitive error:nil];//测试出生日期的合法性
            }
            else
            {
                regularExpression = [[NSRegularExpression alloc]initWithPattern:@"^[1-9][0-9]{5}[0-9]{2}((01|03|05|07|08|10|12)(0[1-9]|[1-2][0-9]|3[0-1])|(04|06|09|11)(0[1-9]|[1-2][0-9]|30)|02(0[1-9]|1[0-9]|2[0-8]))[0-9]{3}$"
                                                                        options:NSRegularExpressionCaseInsensitive error:nil];//测试出生日期的合法性
            }
            //使用正则表达式匹配字符串 NSMatchingReportProgress:找到最长的匹配字符串后调用block回调
            numberofMatch = [regularExpression numberOfMatchesInString:value
                                                               options:NSMatchingReportProgress
                                                                 range:NSMakeRange(0, value.length)];
            
            if(numberofMatch >0)
            {
                return YES;
            }
            else
            {
                return NO;
            }
        case 18:
            year = [value substringWithRange:NSMakeRange(6,4)].intValue;
            if (year %4 ==0 || (year %100 ==0 && year %4 ==0))
            {
                regularExpression = [[NSRegularExpression alloc]initWithPattern:@"^((1[1-5])|(2[1-3])|(3[1-7])|(4[1-6])|(5[0-4])|(6[1-5])|71|(8[12])|91)\\d{4}(((19|20)\\d{2}(0[13-9]|1[012])(0[1-9]|[12]\\d|30))|((19|20)\\d{2}(0[13578]|1[02])31)|((19|20)\\d{2}02(0[1-9]|1\\d|2[0-8]))|((19|20)([13579][26]|[2468][048]|0[048])0229))\\d{3}(\\d|X|x)?$" options:NSRegularExpressionCaseInsensitive error:nil];//测试出生日期的合法性
            }
            else
            {
                regularExpression = [[NSRegularExpression alloc]initWithPattern:@"^((1[1-5])|(2[1-3])|(3[1-7])|(4[1-6])|(5[0-4])|(6[1-5])|71|(8[12])|91)\\d{4}(((19|20)\\d{2}(0[13-9]|1[012])(0[1-9]|[12]\\d|30))|((19|20)\\d{2}(0[13578]|1[02])31)|((19|20)\\d{2}02(0[1-9]|1\\d|2[0-8]))|((19|20)([13579][26]|[2468][048]|0[048])0229))\\d{3}(\\d|X|x)?$" options:NSRegularExpressionCaseInsensitive error:nil];//测试出生日期的合法性
            }
            numberofMatch = [regularExpression numberOfMatchesInString:value
                                                               options:NSMatchingReportProgress
                                                                 range:NSMakeRange(0, value.length)];
            
            
            if(numberofMatch >0)
            {
                //1：校验码的计算方法 身份证号码17位数分别乘以不同的系数。从第一位到第十七位的系数分别为：7－9－10－5－8－4－2－1－6－3－7－9－10－5－8－4－2。将这17位数字和系数相乘的结果相加。
                
                int S = [value substringWithRange:NSMakeRange(0,1)].intValue*7 + [value substringWithRange:NSMakeRange(10,1)].intValue *7 + [value substringWithRange:NSMakeRange(1,1)].intValue*9 + [value substringWithRange:NSMakeRange(11,1)].intValue *9 + [value substringWithRange:NSMakeRange(2,1)].intValue*10 + [value substringWithRange:NSMakeRange(12,1)].intValue *10 + [value substringWithRange:NSMakeRange(3,1)].intValue*5 + [value substringWithRange:NSMakeRange(13,1)].intValue *5 + [value substringWithRange:NSMakeRange(4,1)].intValue*8 + [value substringWithRange:NSMakeRange(14,1)].intValue *8 + [value substringWithRange:NSMakeRange(5,1)].intValue*4 + [value substringWithRange:NSMakeRange(15,1)].intValue *4 + [value substringWithRange:NSMakeRange(6,1)].intValue*2 + [value substringWithRange:NSMakeRange(16,1)].intValue *2 + [value substringWithRange:NSMakeRange(7,1)].intValue *1 + [value substringWithRange:NSMakeRange(8,1)].intValue *6 + [value substringWithRange:NSMakeRange(9,1)].intValue *3;
                
                //2：用加出来和除以11，看余数是多少？余数只可能有0－1－2－3－4－5－6－7－8－9－10这11个数字
                int Y = S %11;
                NSString *M =@"F";
                NSString *JYM =@"10X98765432";
                M = [JYM substringWithRange:NSMakeRange(Y,1)];// 3：获取校验位
                
                NSString *lastStr = [value substringWithRange:NSMakeRange(17,1)];
                
                NSLog(@"%@",M);
                NSLog(@"%@",[value substringWithRange:NSMakeRange(17,1)]);
                //4：检测ID的校验位
                if ([lastStr isEqualToString:@"x"])
                {
                    if ([M isEqualToString:@"X"])
                    {
                        return YES;
                    }
                    else
                    {
                        
                        return NO;
                    }
                }
                else
                {
                    if ([M isEqualToString:[value substringWithRange:NSMakeRange(17,1)]])
                    {
                        return YES;
                    }
                    else
                    {
                        return NO;
                    }
                }
            }
            else
            {
                return NO;
            }
        default:
            return NO;
    }
}


#pragma mark - 加密

- (NSString *)ms_MD5String
{
    const char *cStr = [self UTF8String];
    unsigned char digest[CC_MD5_DIGEST_LENGTH];
    CC_MD5( cStr, (CC_LONG)strlen(cStr), digest ); // This is the md5 call
    
    NSMutableString *output = [NSMutableString stringWithCapacity:CC_MD5_DIGEST_LENGTH * 2];
    
    for(int i = 0; i < CC_MD5_DIGEST_LENGTH; i++)
        [output appendFormat:@"%02x", digest[i]];
    
    return  output;
}

- (NSString *)ms_base64EncodedString
{
    NSData *data = [self dataUsingEncoding:NSUTF8StringEncoding];
    
    return [data base64EncodedStringWithOptions:0];
}

- (NSString *)ms_stringWithBase64EndodedString
{
    NSData *data = [[NSData alloc] initWithBase64EncodedString:self options:0];
    
    return [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
}

@end
